import jsonrpclib
from jsonrpclib.SimpleJSONRPCServer import SimpleJSONRPCServer
import threading
import sys
import random

class Bike:
    def __init__(self,id=0,ip="0.0.0.0",port=6969,localisation=[0,0,0,0]):
        self.id= id
        self.ip = ip
        self.port = port
        self.localisation = localisation
        foo = 'http://'+ip+':'+port
        print foo
        self.services = jsonrpclib.Server(foo)
        self.services.set_id(self.id)

    def get_status(self):
        print "requesting status, plz wait"
        print self.services.status(0)
    
    def remote_unlock(self, unlock_time):
        print "UNLOCKING BIKE %d for %d seconds"%(self.id,unlock_time)
        self.services.unlock(unlock_time)

    def remote_lock(self):
        print "LOCKING BIKE %i! Someone may be hurt, but whatever!"%id
        self.services.lock()

    def print_bike_infos(self):
        print "ID :%s\nIP:%s\nport:%s\nlocalisation:%s\n"%(self.id,self.ip,self.port,self.localisation)


class velov_management:
    def __init__(self):
        self.pool = []
        self.bike_count=0

    def print_infos(self):
        
        for i in range(self.bike_count):
            self.pool[i].print_bike_infos()

    def add_velov(self):
        print "Adding a new velov"
        ip= raw_input("Velov IP PLZ? \n")
        port = raw_input("Velov port PLZ? \n")
        id = self.bike_count
        self.pool.append(Bike(id,ip,port))
        self.bike_count+=1

    def remove_velov(self):
        print "removing!"

    def unlock_velov(self):
        self.print_infos()
        id = raw_input("Wich bike do you want to unlock?\n")
        (self.pool[int(id)]).remote_unlock(random.randint(5,20))
    #Non functional yet
    def lock_velov(self):
        print "Beware of the dragons!"
        self.print_infos()
        id = raw_input("Wich bike do you want to lock?\n")
        if (id <= bike_count):
            (self.bike_pool[id]).remote_lock()
        else:
            print "You want to lock an unexisting bike."

    def get_infos(self):
        self.print_infos()
        id = raw_input("Wich bike do you want to update?\n")
        (self.pool[int(id)]).get_status()

# USELESS
def display_vader():
    art = """\
           _.-'~~~~~~`-._
          /      ||      \\
         /       ||       \\
        |        ||        |
        | _______||_______ |
        |/ ----- \\/ ----- \\|
       /  (     )  (     )  \\
      / \\  ----- () -----  / \\
     /   \\      /||\\      /   \\
    /     \\    /||||\\    /     \\
   /       \\  /||||||\\  /       \\
  /_        \\o========o/        _\\
    `--...__|`-._  _.-'|__...--'
            |    `'    |          
"""
    print art
    print "You really thought I would do that?"

eod = True
def kill_all_kitties():
    #DIRTY ATM
    # TODO : kill server thread gently
    eod=False
    sys.exit(0)


def launch_server_side():
    # We may manage several bikes ;-)
    bike_pool = velov_management()
    while (eod):
        menu = {"1":("Print velo'v information",bike_pool.print_infos),
                "2":("Add a new velov",bike_pool.add_velov),
                "3":("Remove a velov",bike_pool.remove_velov),
                "4":("Manually unlock a velov",bike_pool.unlock_velov),
                "5":("Manually Lock a velov", bike_pool.lock_velov),
                "6":("Refresh infos on a velov", bike_pool.get_infos),
                "7":("Quit",kill_all_kitties),
                "8":("Display a random image of Darth Vader on a unicorn",display_vader)
               }
        for key in sorted(menu.keys()):
             print key+":" + menu[key][0]
        ans = raw_input("Make A Choice :\n")
        menu.get(ans,[None])[1]() 

## Reporting management
## Used for comz direct from the bike : emergency, ...
def battery_alert(bike_id, battery_left):
    print "The bike %i is currently at low level (%i %%) of battery"%(bike_id,battery_left)
    print "You may want to get his location and transfer it to the maintenance crew!"
    # TODO : tell the client to do a position report

def bike_listener(ip='0.0.0.0', port=4242):
    server = SimpleJSONRPCServer(('0.0.0.0',4242))
    server.register_function(battery_alert)
    server.serve_forever()

if __name__ == "__main__":
    server_thread = threading.Thread(target=bike_listener)
    server_thread.start()
    launch_server_side()
        
